package com.only4play.sse.web.resource;

import lombok.extern.slf4j.Slf4j;
import org.springframework.http.MediaType;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.servlet.mvc.method.annotation.SseEmitter;

import java.time.LocalTime;
import java.util.Timer;
import java.util.TimerTask;
import java.util.UUID;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

@Slf4j
@RestController
public class SseController {

    @GetMapping(value = "/stream", produces = MediaType.TEXT_EVENT_STREAM_VALUE)
    public SseEmitter streamMessage() {

        // 设置超时时间，0表示不过期。默认30秒，超过时间未完成会抛出异常：AsyncRequestTimeoutException
        SseEmitter emitter = new SseEmitter(0L);

        ExecutorService sseMvcExecutor = Executors.newSingleThreadExecutor();
        sseMvcExecutor.execute(() -> {
            Timer timer = new Timer();
            // 创建定时器，每 1s 像客户端发送通知时间消息
            timer.scheduleAtFixedRate(new TimerTask() {
                @Override
                public void run() {
                    try {

                        SseEmitter.SseEventBuilder event = SseEmitter.event()
                            .id(UUID.randomUUID().toString().replaceAll("-", ""))
                            .name("SSE EVENT - MVC")
                            .data("SSE MVC - " + LocalTime.now());

                        emitter.send(event);

                    } catch (Exception ex) {
                        emitter.completeWithError(ex);
                    }
                }
            }, 0L, 1000L);
        });

        // complete() 示例
        emitter.onCompletion(() -> log.warn("连接正常完成"));

        // onTimeout(Runnable callback) 示例
        emitter.onTimeout(() -> log.warn("连接超时"));

        // onError(ErrorCallback callback) 示例
        emitter.onError((Throwable t) -> log.warn("发生错误: " + t.getMessage()));

        return emitter;
    }
}
